package com.cryann.mqttserver.mqttProcess.mqttMsgHandler;

import com.cryann.mqttserver.exception.MqttException;
import com.google.common.collect.ImmutableSet;
import io.netty.handler.codec.mqtt.MqttConnectMessage;
import io.netty.handler.codec.mqtt.MqttMessage;
import io.netty.handler.codec.mqtt.MqttMessageType;
import org.apache.commons.lang3.ArrayUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Component;

import java.util.Set;

/**
 * @author cRyann
 * @date 2018/12/28 0028 15:31
 * @description: [MQTT-2.3.1-5] QoS 设置为 0 的 PUBLISH 报文不能包含报文标识符。
 */
@Component
public class MQTT_3$1$2_18 extends AbstractMqttHandler {

    @Override
    protected Set<MqttMessageType> handlerType() {
        return ImmutableSet.of(MqttMessageType.CONNECT);
    }

    @Override
    protected boolean checkMsg(MqttMessage request) {
        MqttConnectMessage message = (MqttConnectMessage) request;
//        TODO 遗嘱标志 Will Flag

        if ( !message.variableHeader().isWillFlag() && message.variableHeader().willQos() != 0 ) {
            throw new MqttException("如果遗嘱标志被设置为0，遗嘱QoS也必须设置为0(0x00) [MQTT-3.1.2-13]。");
        }
        if ( message.variableHeader().isWillFlag() && !ImmutableSet.of(0, 1, 2).contains(message.variableHeader().willQos()) ) {
            throw new MqttException("如果遗嘱标志被设置为1，遗嘱QoS的值可以等于0(0x00)，1(0x01)，2(0x02)。它的值不能等于3 [MQTT-3.1.2-14]。");
        }
        if ( !message.variableHeader().isWillFlag() && message.variableHeader().isWillRetain() ) {
            throw new MqttException("如果遗嘱标志被设置为0，遗嘱保留（Will Retain）标志也必须设置为0 [MQTT-3.1.2-15]。");
        }
        if ( !message.variableHeader().hasUserName() && !message.variableHeader().hasPassword() ) {
            throw new MqttException("如果用户名标志被设置为0，密码标志也必须设置为0 [MQTT-3.1.2-22]。");
        }
        if ( !message.variableHeader().hasUserName() && StringUtils.isNotBlank(message.payload().userName()) ) {
            throw new MqttException("如果用户名（User Name）标志被设置为0，有效载荷中不能包含用户名字段 [MQTT-3.1.2-18]。");
        }
        if ( message.variableHeader().hasUserName() && StringUtils.isBlank(message.payload().userName()) ) {
            throw new MqttException("如果用户名（User Name）标志被设置为1，有效载荷中必须包含用户名字段 [MQTT-3.1.2-19]。");
        }

        if ( !message.variableHeader().hasPassword() && ArrayUtils.isNotEmpty(message.payload().passwordInBytes()) ) {
            throw new MqttException("如果密码（Password）标志被设置为0，有效载荷中不能包含密码字段 [MQTT-3.1.2-20]。");
        }
        if ( message.variableHeader().hasPassword() && ArrayUtils.isEmpty(message.payload().passwordInBytes()) ) {
            throw new MqttException("如果密码（Password）标志被设置为1，有效载荷中必须包含密码字段 [MQTT-3.1.2-21]。");
        }
        return true;
    }
}
